<?php
/**
 * Created by PhpStorm.
 * User: Administrator
 * Date: 2023/3/27
 * Time: 14:44
 */

namespace App\Rep;


use App\Events\OrderEvent;
use App\Exceptions\ApiException;
use App\Models\BalanceHistory;
use App\Models\CheckLog;
use App\Models\Customer;
use App\Models\Employee;
use App\Models\FinishProduct;
use App\Models\Order;
use App\Models\OrderLogistics;
use App\Models\StockAllocationLog;
use http\Env\Request;
use Illuminate\Support\Facades\DB;
use Cisco\Aliyunsms\Facades\Aliyunsms;
use Illuminate\Support\Facades\Log;

class FinishProductRep
{

    /**
     * 获取成品列表
     * 物流状态1：待发货2未发货3已发货4部分待发货5部分未发货
     * @param $params
     */
    public function getFinishProductListRep($params){
        $model = FinishProduct::Search($params)->where('is_stock_up',2)
            ->with(['order','stock_allocation_log','warehouse','customer',
                'order_logistics'=>function($q){
                    $q->with(['image1','image2']);
            },'image1'=>function($q){
                return $q->select('id','file_name','file_url');
            },'image2'=>function($q){
                return $q->select('id','file_name','file_url');
            },'image3'=>function($q){
                return $q->select('id','file_name','file_url');
            },'image4'=>function($q){
                return $q->select('id','file_name','file_url');
            }]);
        $order_type = $params['order_type']??'logistics_product';
        if($order_type != 'finish_product'){
            $list = $model
                //->orderByRaw("FIELD(logistics_status, " . implode(", ", [1, 4, 2, 5,3]) . ")")
                ->orderByRaw("FIELD(logistics_status, 1, 4, 2, 5,3)")
                ->paginate($params['per_page']??10);
        }else{
            $list = $model
                //->orderBy('warehouse_entry_time','desc')
                ->where('logistics_status','<>',3)
                ->orderByRaw("FIELD(logistics_status, 1, 4, 2, 5,3)")
                ->paginate($params['per_page']??10);
        }
        $list = $list->toArray();
        foreach($list['data'] as $k=>$v){
            $image_arr = [];
            if(!empty($v['image1'])){
                $image_arr[] = $v['image1'];
            }
            if(!empty($v['image2'])){
                $image_arr[] = $v['image2'];
            }
            if(!empty($v['image3'])){
                $image_arr[] = $v['image3'];
            }
            if(!empty($v['image4'])){
                $image_arr[] = $v['image4'];
            }

            $list['data'][$k]['image_arr'] = $image_arr;
        }
        return  (object)$list;
    }

    /**
     * 获取备货列表
     */
    public function getStockUpListRep($params){
        $list = FinishProduct::Search($params)->where('is_stock_up',1)
            ->with(['order','stock_allocation_log'])
            ->orderBy('id','desc')->paginate($params['per_page']??10);
        return $list;
    }

    /**
     * 获取当前成品可调货列表
     * @param $params
     */
    public function getStockAllocationListRep($params){
        $finishProduct = FinishProduct::where('id',$params['id'])->first();
        $order = Order::where('id',$finishProduct->order_id)->first();
        //p($finishProduct);
        $list = Order::where('model_number_id',$order->model_number_id)
            ->where('specification_id',$order->specification_id)
            ->where('color_id',$order->color_id)
            ->where(function($q)use($order){
                if(!$order->direction){
                    $q->where('direction','')
                        ->orWhere(function($query){
                            $query->whereNull('direction');
                        });
                }else{
                    $q->where('direction',$order->direction);
                }
            })
            ->where('customer_id','<>',$order->customer_id)
            ->where('production_status',1)
            ->with(['customer'])
            ->paginate($params['per_page']??10);
        //p($list);
        return $list;
    }

    /**
     * 调货
     * @param $params
     */
    public function stockAllocationRep($params){
        DB::beginTransaction();
        try{
            $order = Order::where('id',$params['order_id'])->with('customer')->first();
            $finish_product = FinishProduct::where('id',$params['finish_product_id'])->first();
            $finish_order = Order::where('id',$finish_product->order_id)->first();
            //添加调货记录
            StockAllocationLog::Create([
                'finish_product_id'=>$finish_product->id,
                'order_id'=>$order->id,
//                'finish_customer_name'=>$finish_product->customer->customer_name,
//                'order_customer_name'=>$order->customer->customer_name,
                //'order_number'=>$order->order_number,
                'order_remark'=>$order->remark,
                'finish_order_remark'=>$finish_order->remark,
                'finish_order_id'=>$finish_product->order_id
            ]);
            $order_customer_id = $order->customer_id;
            $finish_product_customer_id = $finish_order->customer_id;
            $order->customer_id = $finish_product_customer_id;
            $order->remark = $finish_order->remark;
            $order->save();
            $finish_order->customer_id = $order_customer_id;
            $finish_order->remark = $order->remark;
            $finish_order->save();
            $finish_product->customer_id = $order_customer_id;
            $finish_product->save();
            DB::commit();
            return ['code'=>0,'msg'=>'success','data'=>[]];

        }catch(\Exception $exception){
            DB::rollBack();
            return ['code'=>2001,'msg'=>$exception->getMessage(),'data'=>[]];
        }
    }

    /**
     * 获取调货记录
     */
    public function getStockAllocationLogRep($params){
        $list = StockAllocationLog::where('finish_product_id',$params['finish_product_id'])
            ->with(['order'=>function($q){
                $q->with('customer');
            },'finish_order'=>function($q){
                $q->with('customer');
            }])
            ->get();
        return $list;
    }


    /**
     * 设置待发货
     * 设置发货状态
     * 物流状态1：待发货2未发货3已发货4部分待发货5部分未发货
     * @param $params
     */
    public function setDeliveryStatusRep($params){
        $ids = $params['ids'];
        $deliveryman = $params['deliveryman'];//送货员
        $logistics_status = $params['logistics_status']??1;
        $remark = $params['remark']??'设置待发货备注';
        DB::beginTransaction();
        try{
            foreach($ids as $k=>$v){
                $logistics_status = 1;
                $finishProduct = FinishProduct::where('id',$v)->first();
                $finishProduct->logistics_status = $logistics_status;
                $finishProduct->save();
                //添加发货记录
                $orderLogisticsRep = new OrderLogisticsRep();
                $orderLogistics = $orderLogisticsRep->addOrderLogistics($finishProduct->id,$finishProduct->order_id,$logistics_status,$remark,$deliveryman,'待发货物流详情');
                $orderLogisticsRep->updateOtherLogisticsStatus($orderLogistics->id);
            }


            DB::commit();
            return ['code'=>0,'data'=>$orderLogistics??[],'msg'=>'success'];
        }catch(\Exception $exception){
            DB::rollBack();
            return ['code'=>1001,'data'=>[],'msg'=>$exception->getMessage()];
        }

    }

    /**
     * 发货
     * @param $params
     * 物流状态1：待发货2未发货3已发货4已签收
     */
    public function DeliverGoodsRep($params){
        //p($params);
        $finish_product_id = $params['finish_product_id'];
        $remark = $params['remark']??'发货备注';
        $logistics_status = $params['logistics_status']??3;
        $logistics_info = $params['logistics_info'];
        $duanxin = $params['duanxin']??'';
        try{
            DB::beginTransaction();
            $finishProduct = FinishProduct::where('id',$finish_product_id)->first();
            $order_logistics = OrderLogistics::where('finish_product_id',$finish_product_id)
                ->where('logistics_status',1)->first();
            $orderLogisticsRep = new OrderLogisticsRep();
            //更新物流信息
            //$OrderLogistics = $orderLogisticsRep->updateOrderLogistics($order_logistics_id,$logistics_status,$logistics_info,$remark);
            $orderLogistics = $orderLogisticsRep->addOrderLogistics(
                $finishProduct->id,
                $finishProduct->order_id,
                $logistics_status,
                $remark,
                $deliveryman='',
                $logistics_info
            );
            //p($order_logistics->id);
            $orderLogisticsRep->updateOtherLogisticsStatus($orderLogistics->id);

            //更新成品物流信息
            $model = FinishProduct::where('id',$finish_product_id)->with(['order'])->first();
            //p($model);
            $model->logistics_status = 3;//已发货
            $model->delivery_time = date('Y-m-d H:i:s');
            $model->save();

            //发短信
            if($duanxin){
                $info = $this->getFinishProductInfoRep($params['id']);
                $res = $this->sendSMS($info);
                if($res['code'] != 0){
                    return $res;
                }
            }
            //event(new OrderEvent($info));
            DB::commit();
            return ['code'=>0,'data'=>$model,'msg'=>'success'];
        }catch(\Exception $exception){
            DB::rollBack();
            return ['code'=>1001,'data'=>[],'msg'=>$exception->getMessage()];
        }

    }



    /**
     * 扫码发货
     * @param $info
     * @return array
     */
    public function deliveryByScanningCodeRep($params){
        if(!empty($params['remark'])){
            $remark = $params['remark'];
        }
        $logistics_status = $params['logistics_status'];
        $logistics_info = $params['logistics_info'];
        $duanxin = $params['duanxin']??'';
        //$finishProduct = FinishProduct::where('id',$params['finish_product_id'])->first();
        $finishProduct = FinishProduct::where('order_id',$params['order_id'])->where('is_del',2)->first();
        $finish_product_id = $finishProduct->id;
        if(!$finishProduct){
            return ['code'=>2000,'data'=>[],'msg'=>'订单不存在或已删除'];
        }
        $orderLogisticsRep = new OrderLogisticsRep();
        DB::beginTransaction();
        try{
            if($finishProduct->logistics_status == 1){
                //待发货：直接发货
                $orderLogistics = $orderLogisticsRep->addOrderLogistics(
                    $finish_product_id,
                    $finishProduct->order_id,
                    $logistics_status,
                    $remark,
                    '',
                    $logistics_info);
                $orderLogisticsRep->updateOtherLogisticsStatus($orderLogistics->id);
                //更新成品物流信息
                $model = FinishProduct::where('id',$finish_product_id)->with(['order'])->first();
                $model->logistics_status = 3;//已发货
                $model->save();

                DB::commit();
                return ['code'=>0,'data'=>$model,'msg'=>'success'];
            }elseif($finishProduct->logistics_status == 2){
                //未发货：直接设置为待发货，然后发货
                return ['code'=>0,'data'=>[],'msg'=>'未设置待发货'];
            }elseif($finishProduct->logistics_status == 3){
                //已发货
                DB::commit();
                return ['code'=>0,'data'=>$finishProduct,'msg'=>'当前订单为已发货状态，请核对信息'];
            }elseif($finishProduct->logistics_status == 4){
                //已签收
                return ['code'=>0,'data'=>$finishProduct,'msg'=>'当前订单为已签收，请核对信息'];
            }
        }catch(\Exception $exception){
            DB::rollBack();
            return ['code'=>1001,'data'=>[],'msg'=>$exception->getMessage()];
        }
    }

    /**
     * 签收上传
     * @param $params
     * @return void
     */
    public function signForExpressDeliveryRep($params){
        if(!empty($params['remark'])){
            $remark = $params['remark'];
        }
        $logistics_status = $params['logistics_status']??4;
        $logistics_info = $params['logistics_info']??'已签收';
        $deliveryman = $params['user_id'];
        $payment = $params['payment'];
        $image1 = $params['image1'];
        $image2 = $params['image2'];
        $received_money = $params['received_money'];
        $finishProduct = FinishProduct::where('order_id',$params['order_id'])->where('is_del',2)->first();
        $finish_product_id = $finishProduct->id;
        if(!$finishProduct){
            return ['code'=>2001,'data'=>[],'msg'=>'订单不存在或已删除'];
        }
        $orderLogisticsRep = new OrderLogisticsRep();
        DB::beginTransaction();
        try{
            if($finishProduct->logistics_status == 1){
                //待发货：直接发货
                return ['code'=>2001,'data'=>[],'msg'=>'当前订单为待发货状态，请核对信息'];
            }elseif($finishProduct->logistics_status == 2){
                //未发货：直接设置为待发货，然后发货
                return ['code'=>2001,'data'=>[],'msg'=>'未设置待发货'];
            }elseif($finishProduct->logistics_status == 3){
                //已发货
                $orderLogistics = $orderLogisticsRep->addOrderLogistics($finish_product_id,$finishProduct->order_id,$logistics_status,$remark,$deliveryman,$logistics_info,$payment,$received_money,$image1,$image2);
                $orderLogisticsRep->updateOtherLogisticsStatus($orderLogistics->id);
                //更新成品物流信息
                $model = FinishProduct::where('id',$finish_product_id)->with(['order'=>function($q){
                    $q->select('id','receivables','received');
                }])->first();
                $model->logistics_status = 4;//已发货
                $model->save();

                DB::commit();
                return ['code'=>0,'data'=>$finishProduct,'msg'=>'success'];
            }elseif($finishProduct->logistics_status == 4){
                //已签收
                return ['code'=>0,'data'=>$finishProduct,'msg'=>'当前订单为已签收，请核对信息'];
            }
        }catch(\Exception $exception){
            DB::rollBack();
            return ['code'=>1001,'data'=>[],'msg'=>$exception->getMessage()];
        }
    }



    /**
     * 取消待发货
     * 1：待发货2未发货3已发货4部分待发货5部分未发货
     */
    public function cancelDeliveryRep($params){
        $order_id = $params['order_id'];
        DB::beginTransaction();
        try{
            $finish = FinishProduct::where('order_id',$order_id)->first();
            if(in_array($finish->logistics_status,[1])){
                $finish->logistics_status = 2;
                $finish->save();
                $model = OrderLogistics::where('order_id',$order_id)->where('logistics_status',1)
                    ->orderBy('id','desc')->first();
                $model->delete();
            }

            DB::commit();
            return ['code'=>0,'data'=>$finish,'msg'=>'success'];
        }catch (\Exception $exception){
            DB::rollBack();
            return ['code'=>1001,'data'=>[],'msg'=>$exception->getMessage()];
        }
    }


    public function sendSMS($info)
    {
        //发送物流通知短信
        $SignName    = env('ALIYUN_SIGN_NAME');          //模板签名
        $TemplateCode= env('ALIYUN_TEMPLATECODE');         //模板CODE
        $customer_name = $info->order->customer->customer_name;
        $product_name = $info->order->product_name->product_name;
        $model_number = $info->order->model_number_name->model_number;
        $delivery_time = $info->delivery_time??date("Y-m-d H:i:s");
        $logistics_info = $info->logistics_info??123456;
        $phone = $info->order->customer->contact_phone;
        //$phone = '15135970424';
        //阿里云模板里面的变量
        $TemplateParam = [
            "customer_name"    => $customer_name,
            "product_name"     => $product_name,
            "model_number"     => $model_number,
            "delivery_time"    => $delivery_time,
            "logistics_info"   => $logistics_info
        ];
        //p($TemplateParam);

        $send = Aliyunsms::sendSms(strval($phone), $SignName, $TemplateCode, $TemplateParam);
        //p($send);
        if ($send->Code == 'OK') {
            $res = ['code'=>0,'msg'=>'success','data'=>''];
        } else {
            $res = ['code'=>3004,'msg'=>$send->Message,'data'=>$send];
        }
        return $res;
    }


    /**
     * 加入成品库
     * @param $order_id
     * @param $semi_finish_product_id
     * @param $num
     * @param $warehouse_id
     * @param $goods_shelf_id
     * @param $model_number_id
     * @param $specification_id
     * @param $color_id
     * @param $direction
     * @param $customer_id
     * @param $is_stock_up
     */
     public function addFinishProductRep($order_id,$semi_finish_product_id,$num,$warehouse_id,$goods_shelf_id,$model_number_id,$specification_id,$color_id,$direction,$customer_id,$is_stock_up,$image_arr = []){
         return FinishProduct::updateOrCreate(['order_id'=>$order_id],
             [
                 'semi_finish_product_id'=>$semi_finish_product_id,
                 'num'=>$num,
                 'warehouse_id'=>$warehouse_id,
                 'goods_shelf_id'=>$goods_shelf_id,
                 'model_number_id'=>$model_number_id,
                 'specification_id'=>$specification_id,
                 'color_id' => $color_id,
                 'direction'=>$direction,
                 'order_id'=> $order_id,
                 'customer_id'=>$customer_id,
                 'warehouse_entry_time'=>date("Y-m-d"),
                 'is_stock_up'=>$is_stock_up,
                 'image1'=>$image_arr[0]??null,
                 'image2'=>$image_arr[1]??null,
                 'image3'=>$image_arr[2]??null,
                 'image4'=>$image_arr[3]??null,
             ]
         );
     }

    /**
     * 设置备货状态
     * @param $params
     */
     public function setStockUpStatusRep($params){
         DB::beginTransaction();
         try{
             $finish = FinishProduct::where('id',$params['id'])->first();
             //备货转成品
             if($params['is_stock_up'] == 2){
                 $allocate_num = $params['allocate_num'];//分配件数
                 if($allocate_num>$finish->num){
                     throw new ApiException(20001,'可分配成品数不足');
                 }elseif($finish->num == $allocate_num){
                     $finish->is_del = 1;
                     $finish->num = 0;
                 }else{
                     $finish->num = $finish->num - $allocate_num;
                 }
                 //$finish->stock_up_remark = $params['stock_up_remark'];
                 $finish->save();

                 $insertArr = [
                     'order_id'=>$finish->order_id,
                     'customer_id'=>$params['customer_id'],
                     'num'=>$allocate_num,
                     'is_stock_up'=>2,
                     'warehouse_id'=>$finish->warehouse_id,
                     'goods_shelf_id'=>$finish->goods_shelf_id,
                     'model_number_id'=>$finish->model_number_id,
                     'specification_id'=>$finish->specification_id,
                     'color_id' => $finish->color_id,
                     'direction'=>$finish->direction,
                     'warehouse_entry_time'=>date("Y-m-d"),
                     'stock_up_remark'=>$params['stock_up_remark']??''
                 ];
                 FinishProduct::insert($insertArr);
             }elseif($params['is_stock_up'] == 1){
                 $finish->is_stock_up = 1;
                 $finish->customer_id=null;
                 $finish->save();
             }

             DB::commit();
             return ['code'=>0,'msg'=>'success','data'=>[]];
         }catch(\Exception $exception){
             DB::rollBack();
             return ['code'=>2001,'msg'=>$exception->getMessage(),'data'=>[]];
         }

     }

    /**
     * 获取成品详情
     */
     public function getFinishProductInfoRep($id){
         $info = FinishProduct::where('id',$id)
             ->with(['order','stock_allocation_log'])
             ->first();
         return $info;
     }

    /**
     * 成品库扣款 / 取消扣款
     * @param $params
     * finish_product_id  成品id
     * is_deduct_money    1：扣款2取消扣款
     *
     */
     public function deductMoneyRep($params){
         $finish_product_id = $params['finish_product_id'];
         $model = FinishProduct::where('id',$finish_product_id)->with(['order'=>function($q){
             $q->select('id','receivables','received','customer_id');
         }])->first();
         $receivables = intval($model->order->receivables);//应收款
         $received = intval($model->order->received);//已收款
         $customer_id = $model->order->customer_id;
         $customer = Customer::where('id',$customer_id)->first();
         $balance = $customer->balance;//余额
         DB::beginTransaction();
         try{
             if($params['is_deduct_money'] == 1){
                 //扣款
                 $after = $balance - ($receivables - $received);
                 $business = '扣款';
                 $model->is_deduct_money = 1;
             }else{
                 //取消扣款
                 $after = $balance + ($receivables - $received);
                 $business = '取消扣款';
                 $model->is_deduct_money = 2;
             }
             $model->save();
             //添加资金变动记录
             $balanceHistoryRep = new BalanceHistoryRep();
             $balanceHistoryRep->addBalanceHistoryRep($customer_id,$receivables,$balance,$after,$model->order_id,$business,$detail='');
             //修改余额
             $customer->balance = $balance - ($receivables - $received);
             $customer->save();

             DB::commit();
             return ['code'=>0,'msg'=>'success','data'=>[]];
         }catch(\Exception $exception){
             DB::rollBack();
             return ['code'=>2001,'msg'=>$exception->getMessage(),'data'=>[]];
         }

     }
     public function updateFinishProductNumRep($params){
         $model = FinishProduct::where('id',$params['id'])->first();
         $model->num = $params['num'];
         $model->save();
         return $model;
     }



    /**
     * 删除成品
     * @param $params
     */
     public function delFinishProductRep($params){
         $finish_product_id = $params['finish_product_id'];
         $model = FinishProduct::where('id',$finish_product_id)->first();
         $model->is_del = 1;
         $model->save();
         return $model;
     }

    /**
     * 扫码盘点
     * @param $params
     */
    public function scanQRCodesCheckRep($params){
        DB::beginTransaction();
        try{
            $finish_product = FinishProduct::where('order_id',$params['order_id'])->first();
            $check_log = new CheckLog();

            $check_log->order_id = $finish_product->order_id;
            $check_log->user_id = $params['user_id'];
            $check_log->check_time = date("Y-m-d H:i:s");
            $check_log->warehouse_id = $params['warehouse_id'];
            $check_log->goods_shelf_id = $params['goods_shelf_id'];
            $check_log->before_num = $finish_product->num;
            $check_log->after_num = $params['after_num'];
            $check_log->save();


            $finish_product->warehouse_id = $params['warehouse_id'];
            $finish_product->goods_shelf_id = $params['goods_shelf_id'];
            //物流状态1：待发货2未发货3已发货4部分待发货5部分未发货
            $logistics_status = $finish_product->logistics_status;
            if(in_array($logistics_status,[1,2,4])){
                if($finish_product->num > $params['after_num']){
                    //盘点数小于订单数
                    if($logistics_status == 2){
                        $finish_product->num = $params['after_num'];
                    }else{
                        $finish_product->num = $params['after_num'];
                        OrderLogistics::where('order_id',$finish_product->order_id)->delete();
                        $finish_product->logistics_status = 1;
                        //添加发货记录
                        $orderLogisticsRep = new OrderLogisticsRep();
                        $remark = '盘点设置代发货';
                        $orderLogistics = $orderLogisticsRep->addOrderLogistics($finish_product->id,$finish_product->order_id,3,$params['after_num'],$remark);
                    }
                }elseif($finish_product->num < $params['after_num']){
                    //盘点数大于订单数
                    $finish_product->num = $params['after_num'];
                    if($logistics_status == 1){
                        $finish_product->logistics_status = 4;
                    }
                }
            }else{
                $finish_product->logistics_status = 2;
                $finish_product->num = $params['after_num'];
            }
            $finish_product->is_check = 1;
            $finish_product->check_time = date("Y-m-d");
            $finish_product->save();
            DB::commit();
            return ['code'=>0,'msg'=>'success','data'=>$finish_product];
        }catch (\Exception $exception){
            DB::rollBack();
            return ['code'=>2001,'msg'=>$exception->getMessage(),'data'=>[]];
        }



    }




}
